<template>
  <div id="formDesign" class="template">
    <left />
    <center />
    <right />
  </div>
</template>
<script>
import left from "./design/left";
import right from "./design/right";
import center from "./design/center";
export default {
  components: { left, right, center },
  data() {
    return {
      dom: null,
      rect: null,
      items: [],
      selectedIndex: -1
    };
  },
  mounted() {
    this.dom = document.querySelector(`#formBody`);
    this.rect = this.dom.getBoundingClientRect();
    this.watchMouseEvent();
  },
  methods: {
    //增加临时表单域，此时鼠标并没有mouseup，新增的表单域也没有rendered，此时增加的表单域随时都有可能被删除；
    addItem(index, flag) {
      if (flag == "next") index = index + 1;
      if (this.items[index] && !this.items[index].rendered) return;
      if (this.items[index - 1] && !this.items[index - 1].rendered) return;
      let tempIndex = this.items.findIndex(v => !v.rendered);
      if (tempIndex >= 0) this.items.splice(tempIndex, 1);
      this.items.splice(index, 0, {
        code: this.$root.form.curField.code,
        children: this.$root.form.curField.children,
        props: this.$root.form.curField.props,
        label:this.$root.form.curField.label,
        selected: false,
        rendered: false,
        left: 0,
        right: 0,
        bottom: 0,
        top: 0,
        height: 0,
        width: 0
      });
    }, //鼠标拖拽着一个表单域在设计区移动，计算出鼠标所在表单域列表中的位置
    mouseMoving(x, y) {
      let isIn =
        x >= this.rect.left &&
        x <= this.rect.right &&
        y > this.rect.top &&
        y < this.rect.bottom;
      if (!isIn) return;
      let index = this.items.length - 1;
      let flag = "next";
      for (let i in this.items) {
        let item = this.items[i];
        if (y > item.top && y <= item.bottom) {
          index = parseInt(i);
          let center = item.top + item.height / 2;
          if (y <= center) flag = "pre";
          else flag = "next";
          break;
        }
      }
      this.addItem(index, flag);
    },
    //真正的增加表单域，把临时表单域渲染成真正的表单域，如果鼠标mouseup时没有在设计区，则删除临时表单域
    mouseUp(x, y) {
      this.rect = this.dom.getBoundingClientRect();
      let xIn = x >= this.rect.left && x <= this.rect.right;
      let yIn = y >= this.rect.top && y <= this.rect.bottom;
      let index = this.items.findIndex(v => !v.rendered);
      if (xIn && yIn) {
        this.items[index].rendered = true;
         this.items.forEach(v=>v.selected = false)
        this.items[index].selected = true;
        this.selectedIndex = index;
        this.$root.form.curField = null;
        this.$nextTick(_ => {
          this.getFieldsPosition(index);
        });
      } else {
        this.items.splice(index, 1);
      }
    },
    //插入了新的表单域后，新表单域以及后面的表单域都应重新计算位置，前面的表单域不用重复计算
    getFieldsPosition(index) {
      for (; index < this.items.length; index++) {
        let item = this.items[index];
        let rect = this.dom.children[index].getBoundingClientRect();
        item.left = rect.left;
        item.right = rect.right;
        item.top = rect.top;
        item.bottom = rect.bottom;
        item.height = rect.height;
        item.width = rect.width;
      }
    },
    //监听formDesign的事件，之所以搞这么复杂，是因为此刻鼠标正下方有一个元素，所以触发不了本组件的enter事件
    watchMouseEvent() {
      let parentDom = document.querySelector("#formDesign");
      parentDom.addEventListener("mousemove", e => {
        if (!this.$root.form.curField) return;
        this.mouseMoving(e.clientX, e.clientY);
      });
      parentDom.addEventListener("mouseup", e => {
        if (!this.$root.form.curField) return;
        this.mouseUp(e.clientX, e.clientY);
      });
    }
  }
};
</script>

<style lang="scss" scoped>
.template {
  display: flex;
  height: calc(100% + 36px);
  margin: -18px;
}
</style>